#include "thread_pool.h"

// 每一个子线程的线程函数入口
void *threadFunc(void *arg)
{
    // 先获取到线程池
    threadpool_t *threadpool = (threadpool_t *)arg;
    while (1)
    {
        task_t *task = taskDequeue(&threadpool->queue);
        if (task)
        {
            int peerfd = task->peerfd;
            char username[1000] = {0};
            // 如果未登录，执行登录验证
            while (!task->is_logged)
            {
                int ret = user_login(peerfd, username);
                if (ret == 0)
                {
                    task->is_logged = 1; // 登录成功
                    char info_content[1024] = {0};
                    sprintf(info_content, "USER %s LOGIN SUCCESS", username);
                    LOG_INFO("LOGIN", info_content);
                }
                else
                {
                    continue;
                }
            }

            // 持续处理客户端消息
            while (1)
            {
                pwdCommand(task);
                int ret = handleMessage(task);
                if (ret == 0)
                {
                    break; // 客户端断开连接
                }
            }

            close(peerfd);
            free(task); // 释放任务节点
        }
        else
        {
            break; // 退出子线程
        }
    }
    return NULL;
}

void threadpoolInit(threadpool_t *threadpool, int num)
{
    if (threadpool)
    {
        threadpool->pthreads = (pthread_t *)calloc(num, sizeof(pthread_t));
        threadpool->threadNum = num;
        queueInit(&threadpool->queue);
    }
}

void threadpoolDestroy(threadpool_t *threadpool)
{
    if (threadpool)
    {
        free(threadpool->pthreads);
        queueDestroy(&threadpool->queue);
    }
}

void threadpoolStart(threadpool_t *threadpool)
{
    if (threadpool)
    {
        for (int i = 0; i < threadpool->threadNum; ++i)
        {
            int ret = pthread_create(
                &threadpool->pthreads[i],
                NULL,
                threadFunc,
                threadpool);
            THREAD_ERROR_CHECK(ret, "pthread_create");
            printf("sub thread %ld\n", threadpool->pthreads[i]);
        }
    }
}

void threadpoolStop(threadpool_t *threadpool)
{
    // 当任务队列中还有元素时,应该要继续执行
    while (!queueIsEmpty(&threadpool->queue))
    {
        sleep(1);
    }

    // 通知所有的子线程退出
    broadcastAll(&threadpool->queue);
    // 回收子线程的资源
    for (int i = 0; i < threadpool->threadNum; ++i)
    {
        pthread_join(threadpool->pthreads[i], NULL);
        printf("sub thread %ld join.\n", threadpool->pthreads[i]);
    }
}
